package calendar

import (
	"github.com/templui/templui/internal/components/icon"
	"github.com/templui/templui/internal/utils"
	"strconv"
	"time"
)

type LocaleTag string

var (
	LocaleDefaultTag    = LocaleTag("en-US")
	LocaleTagChinese    = LocaleTag("zh-CN")
	LocaleTagFrench     = LocaleTag("fr-FR")
	LocaleTagGerman     = LocaleTag("de-DE")
	LocaleTagItalian    = LocaleTag("it-IT")
	LocaleTagJapanese   = LocaleTag("ja-JP")
	LocaleTagPortuguese = LocaleTag("pt-PT")
	LocaleTagSpanish    = LocaleTag("es-ES")
)

type Day int

var (
	Sunday    = Day(0)
	Monday    = Day(1)
	Tuesday   = Day(2)
	Wednesday = Day(3)
	Thursday  = Day(4)
	Friday    = Day(5)
	Saturday  = Day(6)
)

type Props struct {
	ID                string
	Class             string
	LocaleTag         LocaleTag
	Value             *time.Time
	Name              string
	InitialMonth      int  // Optional: 0-11 (Default: current or from Value). Controls the initially displayed month view.
	InitialYear       int  // Optional: (Default: current or from Value). Controls the initially displayed year view.
	StartOfWeek       *Day // Optional: 0-6 [Sun-Sat] (Default: 1).
	RenderHiddenInput bool // Optional: Whether to render the hidden input (Default: true). Set to false when used inside DatePicker.
}

templ Calendar(props ...Props) {
	{{
		var p Props
		if len(props) > 0 {
			p = props[0]
		}
		if p.ID == "" {
			p.ID = utils.RandomID() + "-calendar"
		}
		if p.Name == "" {
			// Should be provided by parent (e.g., DatePicker or in standalone usage)
			p.Name = p.ID + "-value" // Fallback name
		}
		if p.LocaleTag == "" {
			p.LocaleTag = LocaleDefaultTag
		}
		// Default to rendering hidden input unless explicitly set to false
		if p.RenderHiddenInput == false && len(props) > 0 {
			// Only respect false if it was explicitly passed
			p.RenderHiddenInput = props[0].RenderHiddenInput
		} else {
			p.RenderHiddenInput = true
		}

		initialStartOfWeek := Monday
		if p.StartOfWeek != nil {
			initialStartOfWeek = *p.StartOfWeek
		}

		initialView := time.Now()
		if p.Value != nil {
			initialView = *p.Value
		}

		initialMonth := p.InitialMonth
		initialYear := p.InitialYear

		// Use year from initialView if InitialYear prop is invalid/unset (<= 0)
		if initialYear <= 0 {
			initialYear = initialView.Year()
		}

		// Use month from initialView if InitialMonth prop is invalid OR
		// if InitialMonth is default 0 AND InitialYear was also defaulted (meaning neither was likely set explicitly)
		if (initialMonth < 0 || initialMonth > 11) || (initialMonth == 0 && p.InitialYear <= 0) {
			initialMonth = int(initialView.Month()) - 1 // time.Month is 1-12
		}

		initialSelectedISO := ""
		if p.Value != nil {
			initialSelectedISO = p.Value.Format("2006-01-02")
		}

		// For SelectBox display
		currentMonth := initialMonth
		currentYear := initialYear

		// Generate short month names (English only, JS will update with localized)
		monthNames := []string{"Jan", "Feb", "Mar", "Apr", "May", "Jun", "Jul", "Aug", "Sep", "Oct", "Nov", "Dec"}
	}}
	<div class={ p.Class } id={ p.ID + "-wrapper" } data-tui-calendar-wrapper="true">
		if p.RenderHiddenInput {
			<input
				type="hidden"
				name={ p.Name }
				value={ initialSelectedISO }
				id={ p.ID + "-hidden" }
				data-tui-calendar-hidden-input
			/>
		}
		<div
			id={ p.ID }
			data-tui-calendar-container="true"
			data-tui-calendar-locale-tag={ string(p.LocaleTag) }
			data-tui-calendar-initial-month={ strconv.Itoa(initialMonth) }
			data-tui-calendar-initial-year={ strconv.Itoa(initialYear) }
			data-tui-calendar-selected-date={ initialSelectedISO }
			data-tui-calendar-start-of-week={ int(initialStartOfWeek) }
		>
			<!-- Calendar Header -->
			<div class="flex items-center gap-2 mb-4">
				<button
					type="button"
					data-tui-calendar-prev
					class="inline-flex items-center justify-center rounded-md text-sm font-medium h-7 w-7 hover:bg-accent hover:text-accent-foreground focus:outline-none disabled:opacity-50 shrink-0"
				>
					@icon.ChevronLeft()
				</button>
				<div class="flex gap-2 flex-1 min-w-0">
					<!-- Month Select -->
					<div class="relative flex-1 has-[:focus]:border-ring border border-input shadow-xs has-[:focus]:ring-ring/50 has-[:focus]:ring-[3px] rounded-md">
						<select
							id={ p.ID + "-month-select" }
							data-tui-calendar-month-select
							class="absolute inset-0 opacity-0 cursor-pointer w-full"
							aria-label="Choose the Month"
						>
							for i := 0; i < 12; i++ {
								<option value={ strconv.Itoa(i) } selected?={ i == currentMonth } data-tui-calendar-month-index={ strconv.Itoa(i) }>
									{ monthNames[i] }
								</option>
							}
						</select>
						<span class="select-none font-medium rounded-md px-2 flex items-center justify-center gap-1 text-sm h-7 pointer-events-none" aria-hidden="true">
							<span id={ p.ID + "-month-value" }>{ monthNames[currentMonth] }</span>
							@icon.ChevronDown(icon.Props{Size: 14, Class: "text-muted-foreground"})
						</span>
					</div>
					<!-- Year Select -->
					<div class="relative flex-1 has-[:focus]:border-ring border border-input shadow-xs has-[:focus]:ring-ring/50 has-[:focus]:ring-[3px] rounded-md">
						<select
							id={ p.ID + "-year-select" }
							data-tui-calendar-year-select
							class="absolute inset-0 opacity-0 cursor-pointer w-full"
							aria-label="Choose the Year"
						>
							for year := 2100; year >= 1900; year-- {
								<option value={ strconv.Itoa(year) } selected?={ year == currentYear }>
									{ strconv.Itoa(year) }
								</option>
							}
						</select>
						<span class="select-none font-medium rounded-md px-2 flex items-center justify-center gap-1 text-sm h-7 pointer-events-none" aria-hidden="true">
							<span id={ p.ID + "-year-value" }>{ strconv.Itoa(currentYear) }</span>
							@icon.ChevronDown(icon.Props{Size: 14, Class: "text-muted-foreground"})
						</span>
					</div>
				</div>
				<button
					type="button"
					data-tui-calendar-next
					class="inline-flex items-center justify-center rounded-md text-sm font-medium h-7 w-7 hover:bg-accent hover:text-accent-foreground focus:outline-none disabled:opacity-50 shrink-0"
				>
					@icon.ChevronRight()
				</button>
			</div>
			<!-- Weekday Headers -->
			<div data-tui-calendar-weekdays class="grid grid-cols-7 gap-1 mb-1 place-items-center"></div>
			<!-- Calendar Day Grid -->
			<div data-tui-calendar-days class="grid grid-cols-7 gap-1 place-items-center"></div>
		</div>
	</div>
}
